package com.hp.team.bookstore.dbutil.dao;

import org.hibernate.Session;

import com.hp.team.bookstore.dbutil.dao.catalog.ProductHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.catalog.VendorHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.order.OrderHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.order.PORequirementHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.order.PurchaseOrderHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.order.PurchaseOrderItemHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.order.SalesOrderHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.order.SalesOrderItemHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.profile.CustomerHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.profile.RoleHibernateDAO;
import com.hp.team.bookstore.dbutil.dao.profile.UserHibernateDAO;
import com.hp.team.bookstore.model.order.Order;
import com.hp.team.bookstore.model.order.PurchaseOrder;
import com.hp.team.bookstore.model.order.SalesOrder;

public class DAOFactory {

	public UserHibernateDAO getUserDAO() {
		return (UserHibernateDAO) instantiateDAO(UserHibernateDAO.class);
	}

	public RoleHibernateDAO getRoleDAO() {
		return (RoleHibernateDAO) instantiateDAO(RoleHibernateDAO.class);
	}
	
	public CustomerHibernateDAO getCustomerDAO() {
		return (CustomerHibernateDAO) instantiateDAO(CustomerHibernateDAO.class);
	}

	public ProductHibernateDAO getProductDAO() {
		return (ProductHibernateDAO) instantiateDAO(ProductHibernateDAO.class);
	}
	
	public VendorHibernateDAO getVendorDAO() {
		return (VendorHibernateDAO) instantiateDAO(VendorHibernateDAO.class);
	}
	
	public PurchaseOrderHibernateDAO getPurchaseOrderDAO() {
		return (PurchaseOrderHibernateDAO) instantiateDAO(PurchaseOrderHibernateDAO.class);
	}

	public SalesOrderHibernateDAO getSalesOrderDAO() {
		return (SalesOrderHibernateDAO) instantiateDAO(SalesOrderHibernateDAO.class);
	}
	
	public PurchaseOrderItemHibernateDAO getPurchaseOrderItemDAO() {
		return (PurchaseOrderItemHibernateDAO) instantiateDAO(PurchaseOrderItemHibernateDAO.class);
	}

	public SalesOrderItemHibernateDAO getSalesOrderItemDAO() {
		return (SalesOrderItemHibernateDAO) instantiateDAO(SalesOrderItemHibernateDAO.class);
	}
	
	public PORequirementHibernateDAO getPORequirementDAO() {
		return (PORequirementHibernateDAO) instantiateDAO(PORequirementHibernateDAO.class);
	}

	@SuppressWarnings("unchecked")
	public <T extends Order> OrderHibernateDAO<T> getOrderDAO(Class<T> clazz) {
		if (clazz == null) {
			throw new IllegalArgumentException();
		}

		if (PurchaseOrder.class.equals(clazz)) {
			return (OrderHibernateDAO<T>) instantiateDAO(PurchaseOrderHibernateDAO.class);
		} else if (SalesOrder.class.equals(clazz)) {
			return (OrderHibernateDAO<T>) instantiateDAO(PurchaseOrderHibernateDAO.class);
		}

		return null;
	}

	@SuppressWarnings("rawtypes")
	private GenericHibernateDAO instantiateDAO(Class daoClass) {

		try {
			GenericHibernateDAO dao = (GenericHibernateDAO) daoClass.newInstance();
			dao.setSession(getCurrentSession());
			return dao;
		} catch (Exception ex) {
			throw new RuntimeException("Can not instantiate DAO: " + daoClass, ex);
		}
	}

	protected Session getCurrentSession() {
		return HibernateUtil.getSessionFactory().getCurrentSession();
	}

}
